// Licensed to Elasticsearch B.V under one or more agreements.
// Elasticsearch B.V licenses this file to you under the Apache 2.0 License.
// See the LICENSE file in the project root for more information.
//
// ███╗   ██╗ ██████╗ ████████╗██╗ ██████╗███████╗
// ████╗  ██║██╔═══██╗╚══██╔══╝██║██╔════╝██╔════╝
// ██╔██╗ ██║██║   ██║   ██║   ██║██║     █████╗
// ██║╚██╗██║██║   ██║   ██║   ██║██║     ██╔══╝
// ██║ ╚████║╚██████╔╝   ██║   ██║╚██████╗███████╗
// ╚═╝  ╚═══╝ ╚═════╝    ╚═╝   ╚═╝ ╚═════╝╚══════╝
// ------------------------------------------------
//
// This file is automatically generated.
// Please do not edit these files manually.
//
// ------------------------------------------------

#nullable restore

using Elastic.Clients.Elasticsearch.Fluent;
using Elastic.Clients.Elasticsearch.Requests;
using Elastic.Clients.Elasticsearch.Serialization;
using Elastic.Transport;
using Elastic.Transport.Extensions;
using System;
using System.Collections.Generic;
using System.Linq.Expressions;
using System.Text.Json;
using System.Text.Json.Serialization;

namespace Elastic.Clients.Elasticsearch.CrossClusterReplication;

public sealed partial class PutAutoFollowPatternRequestParameters : RequestParameters
{
}

/// <summary>
/// <para>
/// Creates a new named collection of auto-follow patterns against a specified remote cluster. Newly created indices on the remote cluster matching any of the specified patterns will be automatically configured as follower indices.
/// </para>
/// </summary>
public sealed partial class PutAutoFollowPatternRequest : PlainRequest<PutAutoFollowPatternRequestParameters>
{
	public PutAutoFollowPatternRequest(Elastic.Clients.Elasticsearch.Name name) : base(r => r.Required("name", name))
	{
	}

	internal override ApiUrls ApiUrls => ApiUrlLookup.CrossClusterReplicationPutAutoFollowPattern;

	protected override HttpMethod StaticHttpMethod => HttpMethod.PUT;

	internal override bool SupportsBody => true;

	internal override string OperationName => "ccr.put_auto_follow_pattern";

	/// <summary>
	/// <para>
	/// The name of follower index. The template {{leader_index}} can be used to derive the name of the follower index from the name of the leader index. When following a data stream, use {{leader_index}}; CCR does not support changes to the names of a follower data stream’s backing indices.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("follow_index_pattern")]
	public string? FollowIndexPattern { get; set; }

	/// <summary>
	/// <para>
	/// An array of simple index patterns that can be used to exclude indices from being auto-followed. Indices in the remote cluster whose names are matching one or more leader_index_patterns and one or more leader_index_exclusion_patterns won’t be followed.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("leader_index_exclusion_patterns")]
	public ICollection<string>? LeaderIndexExclusionPatterns { get; set; }

	/// <summary>
	/// <para>
	/// An array of simple index patterns to match against indices in the remote cluster specified by the remote_cluster field.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("leader_index_patterns")]
	public ICollection<string>? LeaderIndexPatterns { get; set; }

	/// <summary>
	/// <para>
	/// The maximum number of outstanding reads requests from the remote cluster.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_outstanding_read_requests")]
	public int? MaxOutstandingReadRequests { get; set; }

	/// <summary>
	/// <para>
	/// The maximum number of outstanding reads requests from the remote cluster.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_outstanding_write_requests")]
	public int? MaxOutstandingWriteRequests { get; set; }

	/// <summary>
	/// <para>
	/// The maximum number of operations to pull per read from the remote cluster.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_read_request_operation_count")]
	public int? MaxReadRequestOperationCount { get; set; }

	/// <summary>
	/// <para>
	/// The maximum size in bytes of per read of a batch of operations pulled from the remote cluster.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_read_request_size")]
	public Elastic.Clients.Elasticsearch.ByteSize? MaxReadRequestSize { get; set; }

	/// <summary>
	/// <para>
	/// The maximum time to wait before retrying an operation that failed exceptionally. An exponential backoff strategy is employed when retrying.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_retry_delay")]
	public Elastic.Clients.Elasticsearch.Duration? MaxRetryDelay { get; set; }

	/// <summary>
	/// <para>
	/// The maximum number of operations that can be queued for writing. When this limit is reached, reads from the remote cluster will be deferred until the number of queued operations goes below the limit.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_write_buffer_count")]
	public int? MaxWriteBufferCount { get; set; }

	/// <summary>
	/// <para>
	/// The maximum total bytes of operations that can be queued for writing. When this limit is reached, reads from the remote cluster will be deferred until the total bytes of queued operations goes below the limit.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_write_buffer_size")]
	public Elastic.Clients.Elasticsearch.ByteSize? MaxWriteBufferSize { get; set; }

	/// <summary>
	/// <para>
	/// The maximum number of operations per bulk write request executed on the follower.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_write_request_operation_count")]
	public int? MaxWriteRequestOperationCount { get; set; }

	/// <summary>
	/// <para>
	/// The maximum total bytes of operations per bulk write request executed on the follower.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("max_write_request_size")]
	public Elastic.Clients.Elasticsearch.ByteSize? MaxWriteRequestSize { get; set; }

	/// <summary>
	/// <para>
	/// The maximum time to wait for new operations on the remote cluster when the follower index is synchronized with the leader index. When the timeout has elapsed, the poll for operations will return to the follower so that it can update some statistics. Then the follower will immediately attempt to read from the leader again.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("read_poll_timeout")]
	public Elastic.Clients.Elasticsearch.Duration? ReadPollTimeout { get; set; }

	/// <summary>
	/// <para>
	/// The remote cluster containing the leader indices to match against.
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("remote_cluster")]
	public string RemoteCluster { get; set; }

	/// <summary>
	/// <para>
	/// Settings to override from the leader index. Note that certain settings can not be overrode (e.g., index.number_of_shards).
	/// </para>
	/// </summary>
	[JsonInclude, JsonPropertyName("settings")]
	public IDictionary<string, object>? Settings { get; set; }
}

/// <summary>
/// <para>
/// Creates a new named collection of auto-follow patterns against a specified remote cluster. Newly created indices on the remote cluster matching any of the specified patterns will be automatically configured as follower indices.
/// </para>
/// </summary>
public sealed partial class PutAutoFollowPatternRequestDescriptor : RequestDescriptor<PutAutoFollowPatternRequestDescriptor, PutAutoFollowPatternRequestParameters>
{
	internal PutAutoFollowPatternRequestDescriptor(Action<PutAutoFollowPatternRequestDescriptor> configure) => configure.Invoke(this);

	public PutAutoFollowPatternRequestDescriptor(Elastic.Clients.Elasticsearch.Name name) : base(r => r.Required("name", name))
	{
	}

	internal override ApiUrls ApiUrls => ApiUrlLookup.CrossClusterReplicationPutAutoFollowPattern;

	protected override HttpMethod StaticHttpMethod => HttpMethod.PUT;

	internal override bool SupportsBody => true;

	internal override string OperationName => "ccr.put_auto_follow_pattern";

	public PutAutoFollowPatternRequestDescriptor Name(Elastic.Clients.Elasticsearch.Name name)
	{
		RouteValues.Required("name", name);
		return Self;
	}

	private string? FollowIndexPatternValue { get; set; }
	private ICollection<string>? LeaderIndexExclusionPatternsValue { get; set; }
	private ICollection<string>? LeaderIndexPatternsValue { get; set; }
	private int? MaxOutstandingReadRequestsValue { get; set; }
	private int? MaxOutstandingWriteRequestsValue { get; set; }
	private int? MaxReadRequestOperationCountValue { get; set; }
	private Elastic.Clients.Elasticsearch.ByteSize? MaxReadRequestSizeValue { get; set; }
	private Elastic.Clients.Elasticsearch.Duration? MaxRetryDelayValue { get; set; }
	private int? MaxWriteBufferCountValue { get; set; }
	private Elastic.Clients.Elasticsearch.ByteSize? MaxWriteBufferSizeValue { get; set; }
	private int? MaxWriteRequestOperationCountValue { get; set; }
	private Elastic.Clients.Elasticsearch.ByteSize? MaxWriteRequestSizeValue { get; set; }
	private Elastic.Clients.Elasticsearch.Duration? ReadPollTimeoutValue { get; set; }
	private string RemoteClusterValue { get; set; }
	private IDictionary<string, object>? SettingsValue { get; set; }

	/// <summary>
	/// <para>
	/// The name of follower index. The template {{leader_index}} can be used to derive the name of the follower index from the name of the leader index. When following a data stream, use {{leader_index}}; CCR does not support changes to the names of a follower data stream’s backing indices.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor FollowIndexPattern(string? followIndexPattern)
	{
		FollowIndexPatternValue = followIndexPattern;
		return Self;
	}

	/// <summary>
	/// <para>
	/// An array of simple index patterns that can be used to exclude indices from being auto-followed. Indices in the remote cluster whose names are matching one or more leader_index_patterns and one or more leader_index_exclusion_patterns won’t be followed.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor LeaderIndexExclusionPatterns(ICollection<string>? leaderIndexExclusionPatterns)
	{
		LeaderIndexExclusionPatternsValue = leaderIndexExclusionPatterns;
		return Self;
	}

	/// <summary>
	/// <para>
	/// An array of simple index patterns to match against indices in the remote cluster specified by the remote_cluster field.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor LeaderIndexPatterns(ICollection<string>? leaderIndexPatterns)
	{
		LeaderIndexPatternsValue = leaderIndexPatterns;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum number of outstanding reads requests from the remote cluster.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxOutstandingReadRequests(int? maxOutstandingReadRequests)
	{
		MaxOutstandingReadRequestsValue = maxOutstandingReadRequests;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum number of outstanding reads requests from the remote cluster.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxOutstandingWriteRequests(int? maxOutstandingWriteRequests)
	{
		MaxOutstandingWriteRequestsValue = maxOutstandingWriteRequests;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum number of operations to pull per read from the remote cluster.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxReadRequestOperationCount(int? maxReadRequestOperationCount)
	{
		MaxReadRequestOperationCountValue = maxReadRequestOperationCount;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum size in bytes of per read of a batch of operations pulled from the remote cluster.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxReadRequestSize(Elastic.Clients.Elasticsearch.ByteSize? maxReadRequestSize)
	{
		MaxReadRequestSizeValue = maxReadRequestSize;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum time to wait before retrying an operation that failed exceptionally. An exponential backoff strategy is employed when retrying.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxRetryDelay(Elastic.Clients.Elasticsearch.Duration? maxRetryDelay)
	{
		MaxRetryDelayValue = maxRetryDelay;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum number of operations that can be queued for writing. When this limit is reached, reads from the remote cluster will be deferred until the number of queued operations goes below the limit.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxWriteBufferCount(int? maxWriteBufferCount)
	{
		MaxWriteBufferCountValue = maxWriteBufferCount;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum total bytes of operations that can be queued for writing. When this limit is reached, reads from the remote cluster will be deferred until the total bytes of queued operations goes below the limit.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxWriteBufferSize(Elastic.Clients.Elasticsearch.ByteSize? maxWriteBufferSize)
	{
		MaxWriteBufferSizeValue = maxWriteBufferSize;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum number of operations per bulk write request executed on the follower.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxWriteRequestOperationCount(int? maxWriteRequestOperationCount)
	{
		MaxWriteRequestOperationCountValue = maxWriteRequestOperationCount;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum total bytes of operations per bulk write request executed on the follower.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor MaxWriteRequestSize(Elastic.Clients.Elasticsearch.ByteSize? maxWriteRequestSize)
	{
		MaxWriteRequestSizeValue = maxWriteRequestSize;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The maximum time to wait for new operations on the remote cluster when the follower index is synchronized with the leader index. When the timeout has elapsed, the poll for operations will return to the follower so that it can update some statistics. Then the follower will immediately attempt to read from the leader again.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor ReadPollTimeout(Elastic.Clients.Elasticsearch.Duration? readPollTimeout)
	{
		ReadPollTimeoutValue = readPollTimeout;
		return Self;
	}

	/// <summary>
	/// <para>
	/// The remote cluster containing the leader indices to match against.
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor RemoteCluster(string remoteCluster)
	{
		RemoteClusterValue = remoteCluster;
		return Self;
	}

	/// <summary>
	/// <para>
	/// Settings to override from the leader index. Note that certain settings can not be overrode (e.g., index.number_of_shards).
	/// </para>
	/// </summary>
	public PutAutoFollowPatternRequestDescriptor Settings(Func<FluentDictionary<string, object>, FluentDictionary<string, object>> selector)
	{
		SettingsValue = selector?.Invoke(new FluentDictionary<string, object>());
		return Self;
	}

	protected override void Serialize(Utf8JsonWriter writer, JsonSerializerOptions options, IElasticsearchClientSettings settings)
	{
		writer.WriteStartObject();
		if (!string.IsNullOrEmpty(FollowIndexPatternValue))
		{
			writer.WritePropertyName("follow_index_pattern");
			writer.WriteStringValue(FollowIndexPatternValue);
		}

		if (LeaderIndexExclusionPatternsValue is not null)
		{
			writer.WritePropertyName("leader_index_exclusion_patterns");
			JsonSerializer.Serialize(writer, LeaderIndexExclusionPatternsValue, options);
		}

		if (LeaderIndexPatternsValue is not null)
		{
			writer.WritePropertyName("leader_index_patterns");
			JsonSerializer.Serialize(writer, LeaderIndexPatternsValue, options);
		}

		if (MaxOutstandingReadRequestsValue.HasValue)
		{
			writer.WritePropertyName("max_outstanding_read_requests");
			writer.WriteNumberValue(MaxOutstandingReadRequestsValue.Value);
		}

		if (MaxOutstandingWriteRequestsValue.HasValue)
		{
			writer.WritePropertyName("max_outstanding_write_requests");
			writer.WriteNumberValue(MaxOutstandingWriteRequestsValue.Value);
		}

		if (MaxReadRequestOperationCountValue.HasValue)
		{
			writer.WritePropertyName("max_read_request_operation_count");
			writer.WriteNumberValue(MaxReadRequestOperationCountValue.Value);
		}

		if (MaxReadRequestSizeValue is not null)
		{
			writer.WritePropertyName("max_read_request_size");
			JsonSerializer.Serialize(writer, MaxReadRequestSizeValue, options);
		}

		if (MaxRetryDelayValue is not null)
		{
			writer.WritePropertyName("max_retry_delay");
			JsonSerializer.Serialize(writer, MaxRetryDelayValue, options);
		}

		if (MaxWriteBufferCountValue.HasValue)
		{
			writer.WritePropertyName("max_write_buffer_count");
			writer.WriteNumberValue(MaxWriteBufferCountValue.Value);
		}

		if (MaxWriteBufferSizeValue is not null)
		{
			writer.WritePropertyName("max_write_buffer_size");
			JsonSerializer.Serialize(writer, MaxWriteBufferSizeValue, options);
		}

		if (MaxWriteRequestOperationCountValue.HasValue)
		{
			writer.WritePropertyName("max_write_request_operation_count");
			writer.WriteNumberValue(MaxWriteRequestOperationCountValue.Value);
		}

		if (MaxWriteRequestSizeValue is not null)
		{
			writer.WritePropertyName("max_write_request_size");
			JsonSerializer.Serialize(writer, MaxWriteRequestSizeValue, options);
		}

		if (ReadPollTimeoutValue is not null)
		{
			writer.WritePropertyName("read_poll_timeout");
			JsonSerializer.Serialize(writer, ReadPollTimeoutValue, options);
		}

		writer.WritePropertyName("remote_cluster");
		writer.WriteStringValue(RemoteClusterValue);
		if (SettingsValue is not null)
		{
			writer.WritePropertyName("settings");
			JsonSerializer.Serialize(writer, SettingsValue, options);
		}

		writer.WriteEndObject();
	}
}